class Menu extends PIXI.Container {
	constructor(panelName, width, minHeight, maxHeight) {
		super();

		this._visualY = 0;
		this._items = [];
		this._width = width;
		this._minHeight = minHeight ?? 0;
		this._maxHeight = maxHeight ?? minHeight ?? 99999;
		this.panelName = panelName;

		this.update();
	}

	get items() {
	 	return this._items;
	}

	get selected() {
		for(var i = 0; i < this.items.length; i++)
			if(this.items[i].selected)
				return this.items[i];
	}

	set selected(item) {
		for(var i = 0; i < this.items.length; i++)
			this.items[i].selected = false;

		if(item) item.selected = true;
	}

	get selectedIndex() {
		for(var i = 0; i < this.items.length; i++)
			if(this.items[i].selected)
				return i;

		return -1;
	}

	set selectedIndex(index) {
		for(var i = 0; i < this.items.length; i++)
			this.items[i].selected = i == index;
	}

	up() {
		this.selectedIndex = Math.max(0, this.selectedIndex - 1);

		// 取得显示范围
		if(this._maxHeight) {
			const index = this.selectedIndex;
			var visualY = 0;
			for(var i = 0; i < this.items.length; i++) {
				const item = this.items[i];
				if(index == i) {
					// 如果不在显示范围内
					if(visualY < this._visualY) {
						this._visualY = visualY;
						this.update();
						return;
					}
				}

				visualY = visualY + item.height + 1;
			}
		}
	}

	down() {
		this.selectedIndex = Math.min(this.items.length - 1, this.selectedIndex + 1);

		// 取得显示范围
		if(this._maxHeight) {
			const index = this.selectedIndex;
			var visualY = 24;
			for(var i = 0; i < this.items.length; i++) {
				const item = this.items[i];
				visualY = visualY + item.height + 1;
				if(index == i) {
					// 如果不在显示范围内
					if(visualY > this._visualY + this._maxHeight - 10) {
						this._visualY = Math.max(0, visualY - this._maxHeight + 11);
						this.update();
						return;
					}
				}
			}
		}
	}

	getItem(index) {
		return this._items[index];
	}

	getItemIndex(item) {
		for(var i = 0; i < this._items.length; i++) {
			if(this._items[i] == item)
				return i;
		}

		return -1;
	}

	addItem(item) {
		if(item.constructor.name != "MenuItem")
			throw "Menu child just support class MenuItem";

		this._items.push(item);
		this.update();
	}

	removeItem(item) {
		const index = this.getItemIndex(item);
		if(index>-1) {
			delete this._items[index];
			super.removeItem(item);
			this.update();
		}
	}

	clearItems() {	
        this._items = [];
		this._visualY = 0;
		this.update();
	}

	update() {
		for(var i = 0; i < this.children.length; i++) {
			super.removeChild(this.children[i]);
			i--;
		}

		var height = 24;
		for(var i = 0; i < this._items.length; i++) {
			const item = this._items[i];
			item.y = height - this._visualY;
			height = height + item.height + 1;
		}

		height = height + 10;
		if(height < this._minHeight)
			height = this._minHeight;

		if(this._maxHeight) {
			if(height > this._maxHeight)
				height = this._maxHeight;
		}

		const size = {width:this._width,height};

		// 绘制底板
		const frame = new PIXI.smooth.SmoothGraphics();
		frame.beginFill(0x0000FF, 0.5);
		frame.drawRect(0, 0, size.width, size.height);
		frame.endFill();
		super.addChild(frame);

		// 绘制底部
		const splitMask = new PIXI.smooth.SmoothGraphics();
		splitMask.beginFill(0xE8F880, 1);
		splitMask.drawRect(1, 1, size.width-2, 1);
		splitMask.endFill();

		const split = new PIXI.smooth.SmoothGraphics();
		split.beginFill(0xA8B848, 1);
		split.lineStyle({ color: 0x000000, width: 1, alignment: 0 });
		split.drawRect(0, size.height-8, size.width, 8);
		split.endFill();
		split.addChild(splitMask);
		super.addChild(split);

		// 绘制头部
		const headLiteral = this.panelName;
		const headText = new PIXI.Text(headLiteral, panelHeadStyle);
		headText.x = 20;
		headText.y = 2;
		headText.resolution = 2;

		const headMask = new PIXI.smooth.SmoothGraphics();
		headMask.lineStyle({ color: 0x707020, width: 1, alignment: 0 });
		headMask.beginFill(0xE8F880, 0);
		headMask.drawRect(1, 1, size.width-2, 19);
		headMask.endFill();

		const head = new PIXI.smooth.SmoothGraphics();
		head.beginFill(0xA8B848, 1);
		head.lineStyle({ color: 0x000000, width: 1, alignment: 0 });
		head.drawRect(0, 0, size.width, 21);
		head.endFill();
		head.addChild(headMask);
		head.addChild(splitMask);
		head.addChild(headText);
		super.addChild(head);

		for(var i = 0; i < this._items.length; i++) {
			const item = this._items[i];
			// 如果在显示范围内则添加
			if(item.y > 23 && item.y < this._maxHeight - 11) {
				super.addChild(item);
			}
		}
	}
}

class MenuItem extends PIXI.Container {
	constructor(text, callback) {
		super();

		this._text = text;
		this._selected = true;
		this._enable = true;
		this._buttonVisual = true;
		this.selected = false;
		this.callback = callback;
	}

	get enable() {
		return this._enable;
	}

	set enable(value) {
		if(this._enable!=value) {
			this._enable = value;
			this.update();
		}
	}

	get buttonVisual() {
		return this._buttonVisual;
	}

	set buttonVisual(value) {
		if(this.buttonVisual!=value) {
			this._buttonVisual=value;
			this.update();
		}
	}

	get connectContrl() {
		return this._connectContrl;
	}

	set connectContrl(value) {
		if(this._connectContrl!=value) {
			this._connectContrl=value;
			this.update();
		}
	}

	get icon() {
		return this._icon;
	}

	set icon(value) {
		if(this._icon != value) {
			this._icon = value;
			this.update();
		}
	}

	get selected() {
		return this._selected;
	}

	set selected(value) {
		if(this.selected != value) {
			this._selected = value;
			this.update();
		}
	}

	update() {
		for(var i = 0; i < this.children.length; i++) {
			this.removeChild(this.children[i]);
			i--;
		}

		// 添加icon
		var textX = 32;
		if(this.icon) {
			this.icon.x = textX;
			this.icon.y = 6;
			this.addChild(this.icon);
			textX += 20;
		}

		// 添加文字
		const literal = new PIXI.Text(this._text, this._enable ? this.selected ? selectedStyle : textStyle : unenableStyle);
		literal.x = textX;
		literal.y = 0;
		literal.resolution = 2;
		this.addChild(literal);

		// 添加按钮样式
		if(this.selected && this.buttonVisual) {
			const button = new Button("z", {width:21,height:16});
			button.x = 5;
			button.y = 4;
			button.enable = this.enable;
			this.addChild(button);
		}

		// 添加other
		if(this.connectContrl)
			this.addChild(this.connectContrl);
	}
}